package api

import (
	"errors"
	"ginfast/app/system/dto"
	"ginfast/app/system/model"
	"ginfast/app/system/service"
	"ginfast/configs"
	"ginfast/pkg/ginx"
	"ginfast/pkg/orm"
	"ginfast/util"
	"strconv"
	"time"
)

// User
type User struct {
}

// ListHandler 用户列表
func (User) ListHandler(c *ginx.Context) {
	var p dto.Where
	if err := c.MustBind(&p); err != nil {
		return
	}
	t := c.GetUser()
	if t.UserName != model.UserName {
		p.CreatedBy = t.UserName
	}
	var data []model.User
	total, _ := p.DbModelWhere(&model.User{}).Preload("Dept").Find(&data)
	c.JSONWriteTotal(total, data)
}

// MenuHandler
func (User) MenuHandler(c *ginx.Context) {
	t := c.GetUser()
	menulist, permissions := service.MenuRouter(t.RoleID)
	c.JSONWrite(ginx.H{"menuList": menulist, "permissions": permissions})
}

type userRole struct {
	ID   uint   `json:"id"`
	Name string `json:"name"`
}

type userPost struct {
	ID   uint   `json:"postId"`
	Name string `json:"postName"`
}

// ParamsHandler
func (User) ParamsHandler(c *ginx.Context) {
	t := c.GetUser()
	var roles []userRole
	orm.DB().Model(&model.Role{}).Where("CreatedBy = ?", t.UserName).Scan(&roles)
	var posts []userPost
	orm.DB().Model(&model.Post{}).Scan(&posts)
	c.JSONWrite(ginx.H{"roleList": roles, "posts": posts})
}

// GetHandler
func (User) GetHandler(c *ginx.Context) {
	queryId := c.ParamUInt("id")
	var user model.User
	err := orm.DbFirstByID(&user, queryId)
	c.JSONWrite(ginx.H{"data": user, "roleIds": user.RoleIDs}, err)
}

// AuthRoleHandler
func (User) AuthRoleHandler(c *ginx.Context) {
	id := c.ParamUInt("id")
	var user model.User
	var roles []model.Role
	err := orm.DbFirstByID(&user, id)
	if err == nil {
		t := c.GetUser()
		orm.DbFindBy(&roles, "CreatedBy LIKE ?", t.UserName) // 获取当前用户创建的角色
	}
	c.JSONWrite(ginx.H{"roles": roles, "user": user})
}

// AddHandler 新增用户
func (User) AddHandler(c *ginx.Context) {
	var p model.User
	//获取参数
	err := c.MustBind(&p.UserOpt)
	if err != nil {
		return
	}
	p.CreatedBy = c.GetUser().UserName
	err = service.UserCreate(&p)
	c.JSONWriteError(err)
}

// AddPageHandler 新增界面
func (User) AddPageHandler(c *ginx.Context) {
	// trees, err := buildRoleTree(c)
	// if err != nil {
	// 	ginx.JSONWriteError(err, c)
	// 	return
	// }
	// var posts []model.Post
	// if err := orm.DbFind(&posts); err != nil {
	// 	ginx.JSONWriteError(err, c)
	// 	return
	// }
	// ginx.JSONWriteData(ginx.H{"roles": trees, "posts": posts}, c)
}

// ExportHandler 导出
func (User) ExportHandler(c *ginx.Context) {
	// var users []model.User
	// totalCount, err := orm.DbFindPage(param.PageNum, param.PageSize, param.Where(User), &model.User{}, &users)
	c.JSONWriteData(nil)
}

// ProfileHandler profile
func (User) ProfileHandler(c *ginx.Context) {
	t := c.GetUser()
	var user model.User
	err := orm.DbFirstByID(&user, t.UserID)
	c.JSONWrite(ginx.H{"data": user, "roleGroup": "", "postGroup": ""}, err)
}

type updatePwd struct {
	OldPassword string `form:"oldPassword" binding:"required,min=0,max=30"`
	NewPassword string `form:"newPassword" binding:"required,min=0,max=30"`
}

// ProfileUpdatePwdHandler 重置密码
func (User) ProfileUpdatePwdHandler(c *ginx.Context) {
	var p updatePwd
	if err := c.MustBind(&p); err != nil {
		return
	}
	t := c.GetUser()
	var data model.User
	if err := orm.DbFirstByID(&data, t.UserID); err != nil {
		c.JSONWriteError(err)
		return
	}
	oldPassword := service.UserPassword(&data, p.OldPassword)
	if oldPassword != data.Password {
		c.JSONWriteError(errors.New("old password error"))
		return
	}
	data.Password = service.UserPassword(&data, p.NewPassword)
	err := orm.DbUpdateFields(&data, "Password")
	c.JSONWriteError(err)
}

// UpdateHandler 修改
func (User) UpdateHandler(c *ginx.Context) {
	var p model.User
	err := c.MustBind(&p.UserOpt)
	if err != nil {
		return
	}
	if p.UserName == model.UserName {
		p.RoleIDs = nil
	}
	err = orm.DbUpdateModel(&p)
	c.JSONWriteError(err)
}

type resetPwd struct {
	UserID   uint   `json:"userId"`
	Password string `json:"password"`
}

// ResetPwdHandler 修改密码
func (User) ResetPwdHandler(c *ginx.Context) {
	var p resetPwd
	if err := c.MustBind(&p); err != nil {
		return
	}
	var data model.User
	if err := orm.DbFirstByID(&data, p.UserID); err != nil {
		c.JSONWriteError(err)
		return
	}
	data.Password = service.UserPassword(&data, p.Password)
	err := orm.DbUpdateFields(&data, "Password")
	c.JSONWriteError(err)
}

// DeleteHandler 删除
func (User) DeleteHandler(c *ginx.Context) {
	idstr := c.MustParam("id")
	if idstr == "" {
		return
	}
	ids := util.StringSplit(idstr, ",")
	for i, v := range ids {
		if v == 1 {
			ids[i] = 0
			break
		}
	}
	err := orm.DbDeleteByIDs(&model.User{}, ids)
	c.JSONWriteError(err)
}

// EnableHandler 改变状态
func (User) EnableHandler(c *ginx.Context) {
	var p model.User
	err := c.MustBind(&p)
	if err != nil {
		return
	}
	err = orm.DbUpdateFields(&p, "Status")
	c.JSONWriteError(err)
}

// UpdatePwdHandler 重置密码
func (User) UpdatePwdHandler(c *ginx.Context) {
	var p updatePwd
	if err := c.MustBind(&p); err != nil {
		return
	}
	t := c.GetUser()
	var data model.User
	if err := orm.DbFirstByID(&data, t.UserID); err != nil {
		c.JSONWriteError(err)
		return
	}
	oldPassword := service.UserPassword(&data, p.OldPassword)
	if oldPassword != data.Password {
		c.JSONWriteError(errors.New("old password"))
		return
	}
	data.Password = service.UserPassword(&data, p.NewPassword)
	err := orm.DbUpdateFields(&data, "Password")
	c.JSONWriteError(err)
}

// ProfileAuatarHandler 上传头像
func (User) ProfileAuatarHandler(c *ginx.Context) {
	t := c.GetUser()
	saveDir := configs.Public.Abs("upload")
	fileHead, err := c.FormFile("avatarfile")
	if err == nil {
		curdate := time.Now().UnixNano()
		filename := t.UserName + strconv.FormatInt(curdate, 10) + ".png"
		avatarURL := saveDir + filename
		err = c.SaveUploadedFile(fileHead, avatarURL)
		if err == nil {
			err = orm.DbUpdateValues(&model.User{}, t.UserID, orm.H{"Avatar": avatarURL})
		}
	}
	c.JSONWriteError(err)
}

func (o User) Routers(r *ginx.RouterGroup) {
	r.GET("/list", o.ListHandler)
	r.GET("/menu", o.MenuHandler)
	r.GET("/params", o.ParamsHandler)
	r.GET("/:id", o.GetHandler)
	r.GET("/authRole/:id", o.AuthRoleHandler)
	r.POST("", o.AddHandler)
	r.GET("/export", o.ExportHandler)
	r.PUT("", o.UpdateHandler)
	r.PUT("/resetPwd", o.ResetPwdHandler)
	r.DELETE("/:id", o.DeleteHandler)
	r.PUT("/enable", o.EnableHandler)
	r.GET("/profile", o.ProfileHandler)
	r.PUT("/profile", o.UpdateHandler)
	r.PUT("/profile/updatePwd", o.UpdatePwdHandler)
	r.POST("/profile/avatar", o.ProfileAuatarHandler)
}
